package com.weishenai.customerassistant.controller.weChat;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.weishenai.customerassistant.common.Result;
import com.weishenai.customerassistant.entity.Electrical;
import com.weishenai.customerassistant.entity.FactFinder;
import com.weishenai.customerassistant.entity.MetersResult;
import com.weishenai.customerassistant.service.ElectricalService;
import com.weishenai.customerassistant.service.FactFinderService;
import com.weishenai.customerassistant.service.MetersResultsService;
import com.weishenai.customerassistant.service.PublishingTaskService;
import com.weishenai.customerassistant.utils.DateUtil;
import com.weishenai.customerassistant.utils.UniqueIdUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;

import java.lang.reflect.Field;
import java.util.Set;

@Api(tags = "小程序_勘察报告勘察报告结果")
@Slf4j
@RestController
@RequestMapping("/wechat/result")
public class MetersResultWechatController {

    @Autowired
    private ElectricalService electricalService;
    @Autowired
    private RedisTemplate redisTemplate;
    @Autowired
    private MetersResultsService metersResultsService;
    @Autowired
    private FactFinderService factFinderService;
    @Autowired
    private PublishingTaskService publishingTaskService;

    @Value("${file.imageSavePath}")
    private String fileSavePath;

    @ApiOperation("小程序_插入一条勘察报告结果信息")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "userId", value = "勘查员id"),
            @ApiImplicitParam(name = "eleId", value = "配变id"),
            @ApiImplicitParam(name = "userArea", value = "勘查员所在供电所")
    })
    @PostMapping("/create/{userId}/{eleId}/{userArea}")
    public Object createOneMetersResult(@PathVariable("eleId") Integer eleId,
                                        @RequestBody MetersResult metersResult,
                                        @PathVariable("userId") Integer userId,
                                        @PathVariable("userArea") String userArea) {
        metersResult.setSubstationName(userArea);
        FactFinder factFinder = factFinderService.selectById(userId);
        // 修改任务信息的状态
        publishingTaskService.updateState(factFinder.getWeixinId(),"已勘测",metersResult.getId());
        //设置基础信息
        metersResult.setState("已勘测");
        metersResult.setCustomerId(UniqueIdUtil.getResultId(redisTemplate, false));
        metersResult.setFactFinder(factFinder.getFactName());
        metersResult.setCreatedTime(DateUtil.getTime());
        Electrical electrical = electricalService.selectById(eleId);
        if (electrical == null) return Result.failed("配变id错误");
        //设置配变信息
        metersResult.setCapacity(electrical.getCapacity());
        metersResult.setType(electrical.getType());
        metersResult.setAreaName(electrical.getAreaName());
        metersResult.setRemark(electrical.getRemark());
        metersResult.setRunTimeId(electrical.getRunTimeId());
        metersResult.setElectricalTransformerName(electrical.getElectricalTransformerName());
        metersResult.setPoleId(electrical.getPoleId());
        //检查报告是否符合标准..
        if (checkMetersResult(metersResult)) {
            Integer result = metersResultsService.insertOneMetersResult(metersResult);
            return result > 0 ? Result.success() : Result.failed("失败");
        } else return Result.failed("检查勘察报告结果不符合标准");
    }

    @ApiOperation("小程序_获取工单编号")
    @GetMapping("/getOrderId")
    public Object getOrderId() {
        String resultId = UniqueIdUtil.getResultId(redisTemplate, false);
        log.info("小程序获取的订单编号为:" + resultId);
        return Result.success(resultId);
    }

    @ApiOperation("小程序_根据状态和勘察员姓名查找勘察报告结果")
    @GetMapping("/selectByState/{factFinderName}/{state}/{pageNum}/{pageSize}")
    public Object selectByState(@PathVariable("factFinderName") String factFinderName,
                                @PathVariable("state") String state,
                                @PathVariable(name = "pageNum") Integer pageNum,
                                @PathVariable(name = "pageSize") Integer pageSize) {
        if (factFinderName == null || state == null) return Result.failed("参数不可以为空!");
        IPage<MetersResult> metersResultIPage = metersResultsService.selectByState(factFinderName, state, pageNum, pageSize);
        return Result.success(metersResultIPage);
    }

    @ApiOperation("小程序_根据ID查找一个勘察报告结果")
    @GetMapping("/selectById/{id}")
    public Object selectById(@PathVariable("id") Long id) {
        MetersResult metersResult = metersResultsService.selectById(id);
        return Result.success(metersResult);
    }

    /**
     * 检查勘察报告结果是否符合插入标准
     *
     * @param metersResult 勘察报告
     * @return 是否符合
     */
    private boolean checkMetersResult(MetersResult metersResult) {
        log.info("开始检查勘察报告单信息是否符合标准...");
        Set<String> set = electricalService.selectNames();
        Class cls = metersResult.getClass();
        Field[] fields = cls.getDeclaredFields();
        for (int i = 0; i < fields.length; i++) {
            Field f = fields[i];
            f.setAccessible(true);
            Object result = null;
            try {
                //获取字段结果
                result = (Object) f.get(metersResult);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
                return false;
            }

            if (f.getName().equals("type") || f.getName().equals("lowPressureRod")) {
                continue;
            }

            //判断这个字段结果是不是在数据库当中
            if (f.getName().equals("transformerName")) {
                //不在数据库返回失败
                if (!set.contains(result)) {
                    log.info("属性名:" + f.getName() + "为" + result.toString() + ",不存在数据库，报告单检查失败！");
                    return false;
                }
            }
            //数据为空也返回失败
            if (result == null) {
                log.info("属性名:" + f.getName() + "为空，报告单检查失败！");
                return false;
            }
        }
        log.info("检查完成，勘察报告单符合标准");
        return true;
    }
}
